﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;

namespace Projektarbete
{
    class GenerateMap
    {
        public static void generateMap(ref Tile[][] currentMap, int maxDiggerCount, ref Point rTopLeft, ref Point rBottomRight)
        {
            Tile[][] map = currentMap;

            Point mapSize = new Point(map.Length, map[0].Length);

            Random random = new Random();

            for (int x = 0; x < map.Length; x++)
            {
                for (int y = 0; y < map[0].Length; y++)
                {
                    map[x][y].texture = 0;
                    map[x][y] = new Tile(0, 0);
                }
            }

            List<Digger> diggers = new List<Digger>();
            List<Digger> newDiggers = new List<Digger>();
            List<Digger> inactiveDiggers = new List<Digger>();

            diggers.Add(new Digger(new Point(mapSize.X / 2, mapSize.Y / 2), 0.1f));

            Point topLeft = diggers.First().position;
            Point bottomRight = diggers.First().position;

            int loop = 0;

            while (diggers.Count < maxDiggerCount)
            {
                if (inactiveDiggers.Count == diggers.Count)
                {
                    Digger currentDigger = inactiveDiggers.First();

                    currentDigger.MoveRandomlyIgnoreWalls(map, random, ref topLeft, ref bottomRight);

                    if (currentDigger.FoundWall(map))
                    {
                        currentDigger.Dig(ref map);
                        currentDigger.CloneIntoFreePosition(ref map, ref newDiggers, random);
                    }
                }

                inactiveDiggers.Clear();

                foreach (Digger currentDigger in diggers)
                {
                    if (currentDigger.active)
                    {
                        currentDigger.Dig(ref map);
                        currentDigger.MoveToFreePosition(map, random, ref topLeft, ref bottomRight);
                        currentDigger.CloneIntoFreePosition(ref map, ref newDiggers, random);
                    }
                    else
                        inactiveDiggers.Add(currentDigger);
                }

                foreach (Digger digger in newDiggers)
                    diggers.Add(digger);

                loop++;
            }

            rTopLeft = topLeft;
            rBottomRight = bottomRight;
        }

        public static void FixPillars(ref Tile[][] map, Point topLeft, Point bottomRight, Random random, double pillarRemovalChance)
        {
            for (int y = topLeft.Y; y < bottomRight.Y; y++)
            {
                for (int x = topLeft.X; x < bottomRight.X; x++)
                {
                    if (map[y][x].texture == 0)
                    {
                        int count = 0;

                        for (int yy = y - 1; yy < y + 2; yy++)
                        {
                            for (int xx = x - 1; xx < x + 2; xx++)
                            {
                                if (map[yy][xx].texture == 1)
                                    count++;
                            }
                        }

                        if (count >= 7 && random.NextDouble() < pillarRemovalChance)
                        {
                            map[y][x].texture = 1;
                        }
                    }
                }
            }
        }

        public static Tile[][] ZeroPosition(ref Tile[][] currentMap, Point topLeft, Point bottomRight)
        {
            Tile[][] map;

            map = new Tile[bottomRight.Y - topLeft.Y][];

            for (int y = topLeft.Y; y < bottomRight.Y; y++)
            {
                map[y - topLeft.Y] = new Tile[bottomRight.X - topLeft.X];

                for (int x = topLeft.X; x < bottomRight.X; x++)
                {
                    map[y - topLeft.Y][x - topLeft.X] = currentMap[y][x];
                }
            }

            return map;
        }
    }
}
